﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using System.Web;

namespace DotNet.Utilities
{
    public class IPHelper
    {
        #region 客户端信息
        private static string[] browerNames = { /*"MSIE",*/ "Firefox", "Opera", "Chrome", "Netscape", "Safari", "Lynx", "Konqueror" };
        //private const string[] osNames = { "Win", "Mac", "Linux", "FreeBSD", "SunOS", "OS/2", "AIX", "Bot", "Crawl", "Spider" };

        /// <summary>
        /// 获得浏览器信息
        /// </summary>
        /// <returns></returns>
        public static string GetClientBrower(string agent)
        {
            //string agent = httpContext.Request.ServerVariables["HTTP_USER_AGENT"];
            if (!string.IsNullOrEmpty(agent))
            {
                if (agent.IndexOf("MSIE 6.0") > -1)
                    return "IE 6.0";
                else if (agent.IndexOf("MSIE 7.0") > -1)
                    return "IE 7.0";
                else if (agent.IndexOf("MSIE 8.0") > -1)
                    return "IE 8.0";
                else if (agent.IndexOf("MSIE 9.0") > -1)
                    return "IE 9.0";
                else if (agent.IndexOf("MSIE 10.0") > -1)
                    return "IE 10.0";
                else if (agent.IndexOf("MSIE") > -1)
                    return "IE";
                foreach (string name in browerNames)
                {
                    if (agent.Contains(name))
                        return name;
                }
            }
            return "Other";
        }

        /// <summary>
        /// 获得操作系统信息
        /// </summary>
        /// <returns></returns>
        public static string GetClientOS(string agent)
        {
            string os = string.Empty;
            //string agent = httpContext.Request.ServerVariables["HTTP_USER_AGENT"];
            if (agent == null)
                return "Other";
            if (agent.IndexOf("NT 6.2") > -1)
                os = "Windows 8";
            else if (agent.IndexOf("NT 6.1") > -1)
                os = "Windows 7";
            else if (agent.IndexOf("NT 6.0") > -1)
                os = "Windows Vista";
            else if (agent.IndexOf("NT 5.2") > -1)
                os = "Windows 2003";
            else if (agent.IndexOf("NT 5.1") > -1)
                os = "Windows XP";
            else if (agent.IndexOf("NT 5") > -1)
                os = "Windows 2000";
            else if (agent.IndexOf("NT 4.9") > -1)
                os = "Windows ME";
            else if (agent.IndexOf("NT 4") > -1)
                os = "Windows NT4";
            else if (agent.IndexOf("NT 98") > -1)
                os = "Windows 98";
            else if (agent.IndexOf("NT 95") > -1)
                os = "Windows 95";
            else if (agent.IndexOf("NT") > -1)
                os = "Windows";
            else if (agent.IndexOf("Mac") > -1)
                os = "Mac";
            else if (agent.IndexOf("Linux") > -1)
                os = "Linux";
            else if (agent.IndexOf("FreeBSD") > -1)
                os = "FreeBSD";
            else if (agent.IndexOf("SunOS") > -1)
                os = "SunOS";
            else if (agent.IndexOf("OS/2") > -1)
                os = "OS/2";
            else if (agent.IndexOf("AIX") > -1)
                os = "AIX";
            else if (agent.ToLower().IndexOf("unix") > -1)
                os = "Unix";
            else if (System.Text.RegularExpressions.Regex.IsMatch(agent, @"(Bot|Crawl|Spider)"))
                os = "Spiders";
            else
                os = "Other";
            return os;
        }

        /// <summary>
        /// 判断爬虫名称，不是则返回为空字符串
        /// </summary>
        /// <returns></returns>
        public static string GetSpiderBot(string agent)
        {
            string spiderBot = string.Empty;
            //string agent = httpContext.Request.ServerVariables["HTTP_USER_AGENT"];
            if (agent == null)
                return string.Empty;
            agent = agent.ToLower();
            //判断爬虫为谷歌，googlebot/2.1,googlebot-image/1.0,feedfetcher-google,
            //mediapartners-google,adsbot-google,googlebot-mobile/2.1,googlefriendconnect/1.0            
            if (agent.IndexOf("googlebot-image") > -1)
                spiderBot = "Googlebot-Image";
            else if (agent.IndexOf("googlebot-mobile") > -1)
                spiderBot = "Googlebot-Mobile";
            else if (agent.IndexOf("googlebot") > -1)
                spiderBot = "Googlebot";
            else if (agent.IndexOf("feedfetcher-google") > -1)
                spiderBot = "Feedfetcher-Google";
            else if (agent.IndexOf("mediapartners-google") > -1)
                spiderBot = "Google Adsense";
            else if (agent.IndexOf("adsbot-google") > -1)
                spiderBot = "Google AdWords";
            else if (agent.IndexOf("googlefriendconnect") > -1)
                spiderBot = "GoogleFriendConnect";
            else if (agent.IndexOf("google") > -1)
                spiderBot = "Google";
            //判断爬虫为雅虎 ；yahoo! slurp,yahoo! slurp/3.0,yahoo! slurp china,
            else if (agent.IndexOf("yahoo! slurp;") > -1)
                spiderBot = "Yahoo! Slurp";
            else if (agent.IndexOf("yahoo! slurp/3.0") > -1)
                spiderBot = "Yahoo! Slurp/3.0";
            else if (agent.IndexOf("yahoo! slurp china") > -1)
                spiderBot = "Yahoo! Slurp China";
            else if (agent.IndexOf("yahoofeedseeker/2.0") > -1)
                spiderBot = "YahooFeedSeeker/2.0";
            else if (agent.IndexOf("yahoo-blogs") > -1)
                spiderBot = "Yahoo Blogs";
            else if (agent.IndexOf("yahoo-mmcrawler") > -1)
                spiderBot = "Yahoo Image";
            else if (agent.IndexOf("yahoo contentmatch crawler") > -1)
                spiderBot = "Yahoo AD";
            else if (agent.IndexOf("yahoo") > -1)
                spiderBot = "Yahoo";
            //微软bing ,
            else if (agent.IndexOf("msnbot/1.1") > -1)
                spiderBot = "MSNbot/1.1";
            else if (agent.IndexOf("msnbot/2.0b") > -1)
                spiderBot = "MSNbot/2.0b";
            else if (agent.IndexOf("msrabot/2.0/1.0") > -1)
                spiderBot = "Msrabot/2.0/1.0";
            else if (agent.IndexOf("msnbot-media/1.0") > -1)
                spiderBot = "MSNbot-media/1.0";
            else if (agent.IndexOf("msnbot-products") > -1)
                spiderBot = "MSNBot-Products";
            else if (agent.IndexOf("msnbot-academic") > -1)
                spiderBot = "MSNBot-Academic";
            else if (agent.IndexOf("msnbot-newsblogs") > -1)
                spiderBot = "MSNBot-NewsBlogs";
            else if (agent.IndexOf("msnbot") > -1)
                spiderBot = "MSNBot";
            //百度；baiduspider,baiducustomer,baidu-thumbnail,
            //baiduspider-mobile-gate,baidu-transcoder/1.0.6.0
            else if (agent.IndexOf("baiduspider") > -1)
                spiderBot = "Baiduspider";
            else if (agent.IndexOf("baiducustomer") > -1)
                spiderBot = "BaiduCustomer";
            else if (agent.IndexOf("baidu-thumbnail") > -1)
                spiderBot = "Baidu-Thumbnail";
            else if (agent.IndexOf("baiduspider-mobile-gate") > -1)
                spiderBot = "Baiduspider-Mobile-Gate";
            else if (agent.IndexOf("baidu-transcoder/1.0.6.0") > -1)
                spiderBot = "Baidu-Transcoder/1.0.6.0";
            else if (agent.IndexOf("Baidu") > -1)
                spiderBot = "Baidu";
            //腾讯搜搜soso   
            else if (agent.IndexOf("sosospider") > -1)
                spiderBot = "Sosospider";
            else if (agent.IndexOf("sosoblogspider") > -1)
                spiderBot = "SosoBlogspider";
            else if (agent.IndexOf("sosoimagespider") > -1)
                spiderBot = "SosoImagespider";
            else if (agent.IndexOf("soso") > -1)
                spiderBot = "Soso";
            // 网易有道   
            else if (agent.IndexOf("youdaobot/1.0") > -1)
                spiderBot = "YoudaoBot/1.0";
            else if (agent.IndexOf("yodaobot-image/1.0") > -1)
                spiderBot = "YodaoBot-Image/1.0";
            else if (agent.IndexOf("yodaobot-reader/1.0") > -1)
                spiderBot = "Yodaobot-Reader/1.0";
            else if (agent.IndexOf("youdao") > -1)
                spiderBot = "Youdao";
            //搜狐搜狗   
            //if instr(agent, "sogou web robot") > 0 then bot = "Sogou web robot"  
            //if instr(agent, "sogou web spider/3.0") > 0 then Bot = "Sogou web spider/3.0"  
            //if instr(agent, "sogou web spider/4.0") > 0 then Bot = "Sogou web spider/4.0"  
            //if instr(agent, "sogou head spider/3.0") > 0 then Bot = "Sogou head spider/3.0"  
            //if instr(agent, "sogou-test-spider/4.0") > 0 then Bot = "Sogou-Test-Spider/4.0"  
            //if instr(agent, "sogou orion spider/4.0") > 0 then Bot = "Sogou Orion spider/4.0"  
            else if (agent.IndexOf("sogou") > -1)
                spiderBot = "Sogou";
            //'Alexa   
            else if (agent.IndexOf("ia_archiver") > -1)
                spiderBot = "Alexa Ia_archiver";
            else if (agent.IndexOf("iaarchiver") > -1)
                spiderBot = "Alexa Iaarchiver";
            // 'Cuil   
            else if (agent.IndexOf("twiceler-0.9") > -1)
                spiderBot = "Twiceler-0.9";
            // '奇虎   
            else if (agent.IndexOf("qihoo") > -1)
                spiderBot = "Qihoo";
            // 'ASK.com   
            else if (agent.IndexOf("ask jeeves/teoma") > -1)
                spiderBot = "Ask Jeeves/Teoma";
            #region 其他爬虫信息，暂时不实现
            //if instr(agent, "50.nu/0.01") > 0 then Bot = "50.nu/0.01"  
            // if instr(agent, "aspseek") > 0 then Bot = "ASPSeek"  
            // if instr(agent, "betabot") > 0 then Bot = "betaBot"  
            // if instr(agent, "blogpulselive") > 0 then Bot = "BlogPulseLive"  
            // if instr(agent, "blogpulse (isspider-3.0)") > 0 then Bot = "BlogPulse (ISSpider-3.0)"  
            // if instr(agent, "blogvibebot-v1.1") > 0 then Bot = "BlogVibeBot-v1.1"  
            // if instr(agent, "blogsearch/2") > 0 then Bot = "BlogSearch/2"  
            // if instr(agent, "builtwith/0.3") > 0 then Bot = "BuiltWith/0.3"  
            // if instr(agent, "buzzbot/1.0") > 0 then Bot = "BuzzBot/1.0"  
            // if instr(agent, "daumoa/2.0") > 0 then Bot = "Daumoa/2.0"  
            // if instr(agent, "domaintools") > 0 then Bot = "DomainTools"  
            // if instr(agent, "dotbot/1.1") > 0 then Bot = "DotBot/1.1"  
            // if instr(agent, "eapollobot") > 0 then Bot = "eApolloBot"  
            // if instr(agent, "exabot") > 0 then Bot = "Exabot"  
            // if instr(agent, "fast-webcrawler") > 0 then Bot = "Alltheweb"  
            // if instr(agent, "feedburner/1.0") > 0 then Bot = "FeedBurner/1.0"  
            // if instr(agent, "followsite bot") > 0 then Bot = "FollowSite Bot"  
            // if instr(agent, "gaisbot/3.0") > 0 then Bot = "Gaisbot/3.0"  
            // if instr(agent, "gigabot") > 0 then Bot = "Gigabot"  
            // if instr(agent, "gingercrawler/1.0") > 0 then Bot = "GingerCrawler/1.0"  
            // if instr(agent, "hitcrawler_0.1") > 0 then Bot = "hitcrawler_0.1"  
            // if instr(agent, "iaskspider/1.0") > 0 then Bot = "iaskspider/1.0"  
            // if instr(agent, "iaskspider/2.0") > 0 then Bot = "iaskspider/2.0"  
            // if instr(agent, "iearthworm") > 0 then Bot = "iearthworm"  
            // if instr(agent, "jyxobot/1") > 0 then Bot = "Jyxobot/1"  
            // if instr(agent, "larbin") > 0 then Bot = "Larbin"  
            // if instr(agent, "lanshanbot") > 0 then Bot = "lanshanbot"  
            //if instr(agent, "lycos_spider_(t-rex)") > 0 then Bot = "Lycos"  
            // if instr(agent, "markmonitor robots") > 0 then Bot = "MarkMonitor Robots"  
            // if instr(agent, "mj12bot/v1.2.1") > 0 then Bot = "MJ12bot/v1.2.1"  
            // if instr(agent, "mj12bot/v1.2.2") > 0 then Bot = "MJ12bot/v1.2.2"  
            // if instr(agent, "mj12bot/v1.2.3") > 0 then Bot = "MJ12bot/v1.2.3"  
            // if instr(agent, "mj12bot/v1.2.4") > 0 then Bot = "MJ12bot/v1.2.4"  
            // if instr(agent, "mj12bot/v1.2.5") > 0 then Bot = "MJ12bot/v1.2.5"  
            // if instr(agent, "naverbot/1.0") > 0 then Bot = "NaverBot/1.0"  
            // if instr(agent, "netcraftsurveyagent/1.0") > 0 then Bot = "NetcraftSurveyAgent/1.0"  
            // if instr(agent, "netcraft web server survey") > 0 then Bot = "Netcraft Web Server Survey"  
            // if instr(agent, "page2rss/0.5") > 0 then Bot = "Page2RSS/0.5"  
            // if instr(agent, "panscient.com") > 0 then Bot = "panscient.com"'恶意爬虫   
            // if instr(agent, "pku student spider") > 0 then Bot = "PKU Student Spider"  
            // if instr(agent, "psbot/0.1") > 0 then Bot = "psbot/0.1"  
            // if instr(agent, "scooter") > 0 then Bot = "Altavista"  
            // if instr(agent, "servage robot") > 0 then Bot = "Servage Robot"  
            // if instr(agent, "snapbot") > 0 then Bot = "Snapbot"  
            // if instr(agent, "spinn3r") > 0 then Bot = "Spinn3r"  
            // if instr(agent, "sqworm") > 0 then Bot = "AOL"  
            // if instr(agent, "stealer") > 0 then Bot = "Stealer"  
            // if instr(agent, "tagoobot/3.0") > 0 then Bot = "Tagoobot/3.0"  
            // if instr(agent, "twingly recon") > 0 then Bot = "Twingly Recon"  
            // if instr(agent, "urlfan-bot/1.0") > 0 then Bot = "urlfan-bot/1.0"  
            // if instr(agent, "webalta") > 0 then Bot = "WebAlta"  
            // if instr(agent, "yandex/1.01.001") > 0 then Bot = "Yandex/1.01.001"  
            // if instr(agent, "yeti/1.0") > 0 then Bot = "Yeti/1.0"  
            #endregion
            else if (System.Text.RegularExpressions.Regex.IsMatch(agent, @"(Bot|Crawl|Spider)"))
                spiderBot = "Other Spider";
            return spiderBot;
        }

        //private static string[] acceptLanguage = { "en", "fr", "de","jp","ko","es","sv", "zh-cn", "zh-tw", "zh" };
        /// <summary>
        /// 获取客户端语言
        /// </summary>
        /// <returns></returns>
        public static string GetLangage(string langage)
        {
            // string langage = httpContext.Request.ServerVariables["HTTP_ACCEPT_LANGUAGE"];
            if (!string.IsNullOrEmpty(langage))
            {
                langage = langage.ToLower();
                if (langage.IndexOf(',') > -1)
                    return langage.Substring(0, langage.IndexOf(','));
                else if (langage.IndexOf(';') > -1)
                    return langage.Substring(0, langage.IndexOf(';'));
                else
                    return langage;
                //foreach (string name in acceptLanguage)
                //{
                //    if (langage.Contains(name))
                //        return name;
                //    //else
                //        //return langage;
                //        //return langage.Substring(0, langage.IndexOf(';'));
                //}
            }
            return "";
        }

        /// <summary>
        /// 将获得的ip地址换算成数字字符串
        /// </summary>
        public static string GetClientIPdata(HttpContext httpContext)
        {
            string result = "";//= ClientIP(httpContext);
            //return result;
            string[] ipdata = result.Split(new char[] { '.' });
            Double ipint;
            ipint = Convert.ToDouble(ipdata[0]) * 16777216 + Convert.ToDouble(ipdata[1]) * 65536 + Convert.ToDouble(ipdata[2]) * 256 + Convert.ToDouble(ipdata[3]);
            return Convert.ToString(ipint);
        }

        /// <summary>
        /// 获取客户端真实IP地址(可穿过代理服务器)
        /// </summary>
        /// <returns></returns>
        public static string ClientIP(string result, string remoteAdd, string userHostAddress)
        {

            //string result = String.Empty;
            //httpContext.Request.UserHostAddress
            // httpContext.Request.ServerVariables["REMOTE_ADDR"]
            //result = httpContext.Request.ServerVariables["HTTP_X_FORWARDED_FOR"];
            if (result != null && result != String.Empty)
            {
                //可能有代理 
                if (result.IndexOf(".") == -1)     //没有“.”肯定是非IPv4格式 
                    result = null;
                else
                {
                    if (result.IndexOf(",") != -1)
                    {
                        //有“,”，估计多个代理。取第一个不是内网的IP。 
                        result = result.Replace(" ", "").Replace("'", "");
                        string[] temparyip = result.Split(",;".ToCharArray());
                        for (int i = 0; i < temparyip.Length; i++)
                        {
                            if (IsIPAddress(temparyip[i]) && temparyip[i].Substring(0, 3) != "10." && temparyip[i].Substring(0, 7) != "192.168" && temparyip[i].Substring(0, 7) != "172.16.")
                            {
                                return temparyip[i];     //找到不是内网的地址 
                            }
                        }
                    }
                    else if (IsIPAddress(result)) //代理即是IP格式 
                        return result;
                    else
                        result = null;     //代理中的内容 非IP，取IP 
                }

            }

            string IpAddress = (result != null && result != String.Empty) ? result : remoteAdd;

            if (null == result || result == String.Empty)
                result = remoteAdd;

            if (result == null || result == String.Empty)
                result = userHostAddress;

            return result;
        }

        #region bool IsIPAddress(str1) 判断是否是IP格式
        /// <summary>
        /// 判断是否是IP地址格式 0.0.0.0
        /// </summary>
        /// <param name="str1">待判断的IP地址</param>
        /// <returns>true or false</returns>
        public static bool IsIPAddress(string str1)
        {
            if (str1 == null || str1 == string.Empty || str1.Length < 7 || str1.Length > 15) return false;

            string regformat = @"^\d{1,3}[\.]\d{1,3}[\.]\d{1,3}[\.]\d{1,3}$";

            Regex regex = new Regex(regformat, RegexOptions.IgnoreCase);
            return regex.IsMatch(str1);
        }
        #endregion

        #endregion
    }
}
